package com.xiaoyu.lanling.router.deeplink;

import android.content.Context;
import android.content.Intent;
import android.net.Uri;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import com.xiaoyu.lanling.data.ConfigData;
import com.xiaoyu.lanling.log.AppLogClient;

import in.srain.cube.request.JsonData;
import in.srain.cube.util.CLog;
import in.srain.cube.util.CheckUtil;
import in.srain.cube.util.UTUtil;
import in.srain.cube.util.log.LogEvent;

public class DeepLinkRouter {

    private static final String TAG = "DeepLinkRouter";
    private static final DeepLinkRouter INSTANCE = new DeepLinkRouter();

    private final DeepLinkLoader mLoader;
    private final DeepLinkDispatcher mDispatcher;

    public static DeepLinkRouter getInstance() {
        return INSTANCE;
    }

    private DeepLinkRouter() {
        mLoader = new DeepLinkLoader();
        mDispatcher = new DeepLinkDispatcher(mLoader);
    }

    public void updateForRouterConfig(JsonData listJson) {
        mLoader.updateForRouterConfig(listJson);
    }

    public void updateWeexNotNeedLoginConfig(@NonNull String url) {
        mLoader.updateWeexNotNeedLoginConfig(url);
    }

    public boolean dispatch(@NonNull Context context, @NonNull Intent sourceIntent) {
        CheckUtil.checkNotNull(sourceIntent, "sourceIntent cannot be null");
        CheckUtil.checkNotNull(sourceIntent.getData(), "uri in sourceIntent cannot be null");
        CLog.i(TAG, "dispatchEntry: sourceIntent: %s", sourceIntent);
        return dispatchInternal(context, sourceIntent.getData(), sourceIntent);
    }

    public boolean dispatch(@NonNull Context context, @NonNull String url) {
        return dispatchInternal(context, Uri.parse(url), null);
    }

    public boolean dispatch(@NonNull Context context, @NonNull String url, @Nullable Intent sourceIntent) {
        return dispatchInternal(context, Uri.parse(url), sourceIntent);
    }

    public boolean dispatch(@NonNull Context context, @NonNull Uri uri) {
        return dispatchInternal(context, uri, null);
    }

    public boolean dispatch(@NonNull Context context, @NonNull Uri uri, @Nullable Intent sourceIntent) {
        return dispatchInternal(context, uri, sourceIntent);
    }

    private boolean dispatchInternal(@NonNull Context context, @NonNull Uri uri, @Nullable Intent sourceIntent) {
        processIfTableEmpty();
        return mDispatcher.dispatch(context, uri, sourceIntent);
    }

    private void processIfTableEmpty() {
        if (mLoader.isTableEmpty()) {
            final LogEvent logEvent = new LogEvent("deep-link-router");

            String tagMessage = "router table empty, reload config from local";
            CLog.w(TAG, tagMessage);
            logEventForProcessIfTableEmpty(logEvent, tagMessage);

            ConfigData.getInstance().loadConfigFromLocal();

            if (mLoader.isTableEmpty()) {
                tagMessage = "router table still empty after reload config from local";
                CLog.w(TAG, tagMessage);
                logEventForProcessIfTableEmpty(logEvent, tagMessage);
            } else {
                tagMessage = "router table not empty after reload config from local";
                CLog.i(TAG, tagMessage);
                logEventForProcessIfTableEmpty(logEvent, tagMessage);
            }
        }
    }

    private void logEventForProcessIfTableEmpty(LogEvent logEvent, String tagMessage) {
        logEvent.putData("log", tagMessage);
        AppLogClient.Companion.getInstance().addLog(logEvent);
    }

    public void tryDispatcherPendingUri(Context context) {
        mDispatcher.tryDispatcherPendingEntry(context);
    }

    public void tryDispatcherPushPendingUri(@NonNull Context context, @NonNull Uri uri) {
        mDispatcher.dispatchPending(context, uri);
    }
}